﻿using System;

namespace Microsoft.Popfly.GameCreator.GameEngine.Events
{
    public static class MouseEventCheckerFactory
    {
        public static IEventChecker CreateMouseEventChecker(Game game, BehaviorOwner owner, Data.EventInfo eventInfo)
        {
            if (eventInfo.GetType() != typeof(Data.MouseEventInfo))
            {
                throw new ArgumentException(
                    Utils.ErrorMessagePrefix +
                    "CreateMouseEventChecker only accepts EventInfo of type MouseEventInfo.  " +
                    "eventInfo was of type '" + eventInfo.GetType() + "'.");
            }

            Data.MouseEventInfo mouseInfo = (Data.MouseEventInfo)eventInfo;

            BehaviorOwner target = null;
            if (mouseInfo.MouseTarget == null || mouseInfo.MouseTarget == "[self]")
            {
                // Hackiness to match old engine - if there's no target specified, or it's specified as 
                // self, only do it if it's an actor or it's a while down
                if (owner.IsActor || 
                    mouseInfo.MouseType == Data.MouseEventInfo.MouseEventType.WhileMouseLeftButtonDown)
                {
                    target = owner;
                }
                else
                {
                    // Compat: If the owner is a scene, the only valid mouse target is anywhere
                    throw new ArgumentException(
                        "Can only add a mouse listener to a scene when the mouse target is 'Anywhere'."
                        );
                }
            }
            else if (mouseInfo.MouseTarget == "Anywhere")
            {
                target = owner.Scene;
            }
            else
            {
                throw new NotImplementedException(
                    Utils.ErrorMessagePrefix +
                    "CreateMouseEventChecker does not know how to handle a MouseTarget of '" +
                    mouseInfo.MouseTarget + "'.");
            }

            switch (mouseInfo.MouseType)
            {
                case Microsoft.Popfly.GameCreator.Data.MouseEventInfo.MouseEventType.MouseLeftButtonDown :
                    return new MouseLeftButtonDownEventChecker(game, target);

                case Microsoft.Popfly.GameCreator.Data.MouseEventInfo.MouseEventType.MouseLeftButtonUp :
                    return new MouseLeftButtonUpEventChecker(game, target);
                    
                case Microsoft.Popfly.GameCreator.Data.MouseEventInfo.MouseEventType.WhileMouseLeftButtonDown :
                    return new WhileMouseLeftButtonDownEventChecker(game, target);

                case Microsoft.Popfly.GameCreator.Data.MouseEventInfo.MouseEventType.MouseEnter :
                    return new MouseEnterEventChecker(game, target);

                case Microsoft.Popfly.GameCreator.Data.MouseEventInfo.MouseEventType.MouseHover :
                    return new MouseHoverEventChecker(target);

                case Microsoft.Popfly.GameCreator.Data.MouseEventInfo.MouseEventType.MouseLeave :
                    return new MouseLeaveEventChecker(game, target);
                    
                default :
                    throw new NotImplementedException(
                        Utils.ErrorMessagePrefix +
                        "CreateMouseEventChecker doesn't know how to handle MouseEventTypes of '" +
                        mouseInfo.MouseType.ToString() +
                        "'.");
            }

        }
    }
}
